﻿'#define					PACKET_OTHER		0
'#define					PACKET_BYTE			1
'#define					PACKET_BOOL			2
'#define					PACKET_DOUBLE		3
'#define					PACKET_FLOAT		4
'#define					PACKET_LONG			5
'#define					PACKET_ULONG		6
'#define					PACKET_ULLONG		7
'#define					PACKET_STRING		8
'#define					PACKET_16STRING		9
'#define					PACKET_BYTEARRAY	10


Public Enum dataTypes As Byte
    tother = 0
    tbyte = 1
    tbool = 2
    tdouble = 3
    tfloat = 4
    tlong = 5
    tulong = 6
    tullong = 7
    tstring = 8
    t16string = 9
    tbytearray = 10
End Enum

Public Class CPacket

    Private size As Integer = 0
    Private buff() As Byte

    Private packetType As Byte = 0
    Private actionSubType As Byte = 0
    Public targetProcess As UInt32 = 0

    Private pos As Integer = 0

    Public Sub Pack(ByVal _add As Byte(), ByVal length As Integer)
        Try
            ReDim Preserve buff(size + length - 1)
            Dim i As Integer = 0
            For i = 0 To length - 1
                buff(size + i) = _add(i)
            Next
            size += length
            pos = 0
        Catch ex As Exception
            Exit Sub
        End Try
    End Sub

    Private Sub packtype(ByVal tType As dataTypes, ByVal typeSize As Integer)

        Dim b() As Byte
        ReDim b(1)
        b(0) = tType
        Pack(b, 1)

        b = BitConverter.GetBytes(typeSize)
        Pack(b, 4)

    End Sub

    Public Sub Pack(ByVal _add As Integer)
        packtype(dataTypes.tlong, 4)
        Dim b() As Byte = BitConverter.GetBytes(_add)
        Pack(b, 4)
    End Sub

    Public Sub Pack(ByVal _add As String)
        packtype(dataTypes.tstring, _add.Length)
        Dim b() As Byte = System.Text.Encoding.Default.GetBytes(_add)
        Pack(b, _add.Length)
    End Sub

    Public Function UnpackByteRaw() As Byte
        Dim b As Byte = buff(pos)
        pos += 1
        Return b
    End Function

    Public Function UnpackIntRaw() As Integer

        Dim b(4) As Byte
        b(0) = buff(pos)
        b(1) = buff(pos + 1)
        b(2) = buff(pos + 2)
        b(3) = buff(pos + 3)
        pos += 4

        Return BitConverter.ToInt32(b, 0)

    End Function

    Public Function UnpackString() As String

        Dim retval As String = ""
        Dim b As Byte = UnpackByteRaw()
        If b = dataTypes.tstring Then

            Dim len As Integer = UnpackIntRaw()

            For i As Integer = 0 To len - 1

                retval = retval + Chr(UnpackByteRaw)

            Next

        End If

        Return retval

    End Function

    Public Function UnpackInt() As Integer
        If size < 4 Then
            Return 0
        End If
        Dim b() As Byte
        Dim v As Integer = 0
        ReDim b(3)
        Dim i As Integer = 0
        For i = 0 To 4 - 1
            b(i) = buff(pos + i)
        Next
        pos += 4
        v = BitConverter.ToInt32(b, 0)
        Return v
    End Function

    Public Sub SetISetPacketTypeD(ByVal _id As Byte)
        packetType = _id
    End Sub

    Public Function GetID() As Byte
        Return packetType
    End Function

    Public Sub SetSubPacketType(ByVal _id As Byte)
        actionSubType = _id
    End Sub

    Public Function GetSubPacketType() As Byte
        Return actionSubType
    End Function

    Public Function GetSize() As Integer
        Return size
    End Function

    Public Function Transmit(ByRef _s As Net.Sockets.Socket) As Boolean
        '// transmit the data to the remote socket
        Dim t_id As Byte()
        Dim sent As Integer = 0
        Dim chunk As Integer = 512
        Dim thistrans As Integer = 0
        Dim thissent As Integer = 0

        ReDim t_id(0)
        t_id(0) = packetType
        Try
            If _s.Send(t_id, 1, Net.Sockets.SocketFlags.None) > 0 Then

                'now send the sybtype and process id
                t_id(0) = actionSubType
                _s.Send(t_id, 1, Net.Sockets.SocketFlags.None)
                t_id(0) = targetProcess
                _s.Send(t_id, 1, Net.Sockets.SocketFlags.None)

                If _s.Send(BitConverter.GetBytes(size), 4, Net.Sockets.SocketFlags.None) > 0 Then
                    '// now send the payload
                    If size > 0 Then
                        While sent < size
                            thistrans = size - sent
                            If thistrans > 512 Then
                                thistrans = 512
                            End If
                            Dim b() As Byte
                            ReDim b(thistrans - 1)
                            Dim i As Integer = 0
                            For i = 0 To thistrans - 1
                                b(i) = buff(sent + i)
                            Next

                            thissent = _s.Send(b, thistrans, Net.Sockets.SocketFlags.None)
                            sent += thissent
                            '// 2do add in timeout

                        End While

                    End If
                Else
                    Return False
                End If
            Else
                Return False
            End If
        Catch ex As Exception
            Return False
        End Try

    End Function
End Class